import axios from 'axios';
import envConfig from './config';
import utils from '../utils/util';
import store from '../store/index';

const encodeParams = (url) => {
  if (!url) return '';
  let newUrl = url;
  if (/\?.{1,}/.test(url)) {
    const [protocolStr = '', paramsStr] = url.split('?');
    if (paramsStr) {
      try {
        let encodeUrlStr = '';
        paramsStr.split('&').forEach((v, i) => {
          const [key, value] = v.split('=');
          encodeUrlStr += `${i ? '&' : ''}${key}=${value ? encodeURIComponent(value) : ''}`;
        });
        newUrl = `${protocolStr}?${encodeUrlStr}`;
      } catch (e) {}
    }
  }
  return newUrl;
};

// 登录失效
const logOut = () => {
  store.commit('clearUserInfo');
  const { origin, pathname, href } = window.location;
  if (!href.includes('/login')) {
    window.location.href = `${origin}${pathname || '/'}#/login`;
  }
};

/**
 * axios请求方法
 * @param baseURL 请求服务地址
 * @param protocol 协议全名
 * @param options 请求参数
 * @param method 请求方法
 * @param hasQuery 是否为路径传参
 * @param time 超时时间
 * @param showErr 是否显示错误提示
 * @param requestConfig 设置请求配置
 */
const request = ({
  protocol,
  options = {},
  method = 'post',
  showErr = true,
  hasQuery = false,
  time = 1000,
  baseURL = envConfig.baseURL,
  requestConfig = {}
}) => {
  // 允许设置cookie
  // axios.withCredentials = true;
  // axios.defaults.withCredentials = true;
  // axios.defaults.crossDomain = true;
  axios.defaults.timeout = 0;
  const resp = {
    success: false,
    data: null,
    message: '请求失败'
  };
  const requestData = options || {};
  const token = utils.getLocalStorage('x-access-token');
  time = time * 1000;
  // axios请求配置
  const { headers, ...otherConfig } = requestConfig;
  const config = {
    method,
    baseURL,
    url: protocol,
    timeout: 0,
    headers: {
      'Content-Type': 'application/json; charset=UTF-8',
      ...headers,
      'x-access-token': token
    },
    // withCredentials: true,
    // default: {
    //   withCredentials: true,
    //   crossDomain: true
    // },
    ...otherConfig
  };
  if (hasQuery) {
    let urlStr = '';
    Object.keys(requestData).forEach((key, index) => {
      const value = requestData[key] === undefined ? '' : requestData[key];
      urlStr += `${index === 0 ? '?' : '&'}${key}=${value}`;
    });
    config.url = `${protocol}${urlStr}`;
  }
  const methodStr = method.toLowerCase();
  if (methodStr === 'post') {
    config.data = JSON.stringify(requestData);
  } else if (methodStr === 'formdata') {
    config.data = requestData;
    config.method = 'post';
    config.url = encodeParams(config.url);
  } else {
    config.params = requestData;
  }
  return new Promise(async (resolve) => {
    try {
      const res = await axios.request(config);
      if (res.data) {
        const { status, msg, statusText } = res.data;
        resp.data = { ...res.data };
        resp.message = res.statusText || msg || statusText;
        if (String(status) === '200') {
          resp.success = true;
        } else if (String(status) === '201') logOut();
      }
    } catch (error) {
      resp.data = error;
      const response = error.response || {};
      const { data: { code } = {}} = response;
      String(code) === '201' && logOut();
    }
    if (showErr && !resp.success) {
      /* eslint-disable */
      app.$message.error(resp.message);
    }
    if (process.env.NODE_ENV !== 'production') {
      console.log(protocol, resp, requestData);
    }
    resolve(resp);
  });
};

// 上传bimfance
export const uploadRequest = ({
  method = 'post',
  options = {},
  url,
  timeout = 10000,
  headers,
  ...config
}) => {
  return new Promise(async resolve => {
    const reqConfig = {
      method,
      url,
      timeout,
      headers: {
        'Content-Type': 'application/json; charset=UTF-8',
        ...headers
      },
      ...config
    };
    if (method === 'post') {
      reqConfig.data = JSON.stringify(options);
    } else if (method === 'formData') {
      reqConfig.data = options;
      reqConfig.method = 'post';
    } else {
      reqConfig.params = options;
    }
    const result = axios.request(reqConfig);
    resolve(result);
  });
};

export default request;
